package yxmes.tools;

import com.xiaoleilu.hutool.util.StrUtil;

import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.DateFormatUtils;

import io.jboot.app.config.JbootConfigManager;

import java.io.File;
import java.io.FileWriter;
import java.io.InputStream;
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class ServiceCreator {
    final static String SERVICE_PACKAGE = "org.yx.service";
    final static String BASE_SERVICE_PACKAGE = "org.yx.service.core";
    static String PROJECT_PATH = "E:\\java\\idea64\\yxmes";
    static String Developer = "";

    public static void main(String[] args) {
        InputStream in = null;

        try {
            // in =
            // ServiceCreator.class.getClassLoader().getResourceAsStream("application.properties");
            // if (in != null) {
            Properties prop = JbootConfigManager.me().getProperties();
            // Properties prop = new Properties();
            // prop.load(in);
            Developer = prop.getProperty("developer", System.getProperty("user.name"));
            PROJECT_PATH = prop.getProperty("application.service.path").toLowerCase();
            String appName = prop.getProperty("application.context.name").toLowerCase();
            if (StrUtil.isBlank(PROJECT_PATH) || StrUtil.isBlank(appName)
                    || PROJECT_PATH.lastIndexOf("/" + appName + "/") < 0) {
                System.out.println("应用程序配置错误，退出。");
                return;
            }
            int index = PROJECT_PATH.lastIndexOf("/" + appName + "/");

            PROJECT_PATH = PROJECT_PATH.substring(0, index + ("/" + appName + "/").length() - 1);
            // }
        } catch (Exception e) {
            try {
                if (in != null)
                    in.close();
            } catch (Exception e2) {
                // TODO: handle exception
            }
        }

        try {
            final String servicePackagePath = PROJECT_PATH + "\\src\\main\\java\\"
                    + StringUtils.replaceChars(SERVICE_PACKAGE, '.', '\\');

            Scanner sc = new Scanner(System.in);
            System.out.println("输入服务名(例如:CbasViewUserInfoService):");
            String inputStr = sc.nextLine();
            sc.close();
            if (StringUtils.isBlank(inputStr)) {
                System.out.println("无对象可创建，退出。");
                return;
            }

            Pattern pattern = null;
            try {
                pattern = Pattern.compile("^[A-Za-z]+$");
                Matcher matcher = pattern.matcher(inputStr);
                if (!matcher.matches()) {
                    throw new Exception();
                }

            } catch (Exception e) {
                System.out.println("服务名称非法。");
                return;
            }

            if (!inputStr.endsWith("Service")) {
                inputStr += "Service";
            }

            List<Integer> upperIndex = new ArrayList<Integer>();
            StringBuilder sbInputStr = new StringBuilder();
            for (int i = 0; i < inputStr.length(); i++) {
                if (inputStr.charAt(i) >= 'A' && inputStr.charAt(i) <= 'Z') {
                    if (upperIndex.size() > 0) {
                        sbInputStr.append('_');
                    }
                    upperIndex.add(i);
                }

                sbInputStr.append(inputStr.charAt(i));
            }

            String packageName = sbInputStr.toString().toLowerCase();
            String moduleName = packageName.substring(0, packageName.indexOf('_'));
            packageName = packageName.substring(packageName.indexOf('_') + 1, packageName.lastIndexOf('_'));

            if (upperIndex.size() <= 2) {
                throw new Exception("服务名无效.");
            }

            String modulePath = servicePackagePath + "\\" + moduleName;
            System.out.println("modulePath:" + modulePath);
            File moduleDir = new File(modulePath);
            if (!moduleDir.exists() && !moduleDir.mkdir()) {
                throw new Exception("创建模块目录失败。");
            }

            String packPath = modulePath + "\\" + packageName;
            System.out.println("packPath:" + packPath);
            File packDir = new File(packPath);
            if (!packDir.exists() && !packDir.mkdir()) {
                throw new Exception("创建包目录失败。");
            }

            String serviceName = inputStr;
            File javaFile = new File(packPath + "\\" + StrUtil.removeSuffixIgnoreCase(serviceName, "Service")
                    + "In.java");
            if (!javaFile.exists()) {
                javaFile.createNewFile();
            } else {
                System.out.println("=====Service existed=======");
                return;
            }
            FileWriter fw = new FileWriter(javaFile);
            fw.write(createServiceIn(moduleName, packageName, serviceName));
            fw.close();

            javaFile = new File(packPath + "\\" + StrUtil.removeSuffixIgnoreCase(serviceName, "Service") + "Out.java");
            if (!javaFile.exists()) {
                javaFile.createNewFile();
            } else {
                System.out.println("=====Service existed=======");
                return;
            }
            fw = new FileWriter(javaFile);
            fw.write(createServiceOut(moduleName, packageName, serviceName));
            fw.close();

            javaFile = new File(packPath + "\\" + serviceName + ".java");
            if (!javaFile.exists()) {
                javaFile.createNewFile();
            } else {
                System.out.println("=====Service existed=======");
                return;
            }
            fw = new FileWriter(packPath + "\\" + serviceName + ".java");
            fw.write(createService(moduleName, packageName, serviceName));
            fw.close();

            System.out.println("Service created!Refresh your project.服务创建完成，请刷新工程。");
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    private static String createService(String moduleName, String packName, String serviceName) throws Exception {
        StringBuilder sbCode = new StringBuilder();
        sbCode.append("package ").append(SERVICE_PACKAGE).append('.').append(moduleName).append('.').append(packName)
                .append(";\r\n\r\n");
        sbCode.append("import org.yx.utils.BaseService;\r\n\r\n");
        appendComment(sbCode);
        sbCode.append("public class ").append(serviceName).append(" extends BaseService {\r\n");
        String funName = StrUtil.removeSuffixIgnoreCase(serviceName, "Service");
        String funName1 = funName;
        funName = StringUtils.removeStartIgnoreCase(funName, moduleName);
        if (funName.charAt(0) >= 'A' && funName.charAt(0) <= 'Z') {
            funName = (char) (funName.charAt(0) + 32)
                    + StringUtils.removeStart(funName, String.valueOf(funName.charAt(0)));
        }
        sbCode.append("\tpublic ").append(funName1).append("Out ");
        sbCode.append(funName).append('(').append(funName1).append("In in) throws Exception {\r\n");
        sbCode.append("\t\t").append(funName1).append("Out out = new ");
        sbCode.append(funName1).append("Out();\r\n\r\n\t\treturn out;\r\n\t}\r\n}");

        return sbCode.toString();
    }

    private static String createServiceIn(String moduleName, String packName, String serviceName) throws Exception {
        StringBuilder sbCode = new StringBuilder();
        sbCode.append("package ").append(SERVICE_PACKAGE).append('.').append(moduleName).append('.').append(packName)
                .append(";\r\n\r\n");
        sbCode.append("import ").append(BASE_SERVICE_PACKAGE).append(".ServiceIn;\r\n\r\n");
        appendComment(sbCode);
        sbCode.append("public class ").append(StrUtil.removeSuffixIgnoreCase(serviceName, "Service"));
        sbCode.append("In extends ServiceIn {\r\n").append('}');

        return sbCode.toString();
    }

    private static String createServiceOut(String moduleName, String packName, String serviceName) throws Exception {
        StringBuilder sbCode = new StringBuilder();
        sbCode.append("package ").append(SERVICE_PACKAGE).append('.').append(moduleName).append('.').append(packName)
                .append(";\r\n\r\n");
        sbCode.append("import ").append(BASE_SERVICE_PACKAGE).append(".ServiceOut;\r\n\r\n");
        appendComment(sbCode);
        sbCode.append("public class ").append(StrUtil.removeSuffixIgnoreCase(serviceName, "Service"));
        sbCode.append("Out extends ServiceOut {\r\n").append('}');

        return sbCode.toString();
    }

    private static void appendComment(StringBuilder sbCode) {
        sbCode.append("/**\r\n * ");
        if (!StringUtils.isEmpty(Developer))
            sbCode.append("\r\n * @author ").append(Developer);
        sbCode.append("\r\n * @since ").append(DateFormatUtils.format(new Date(), "yyyy/MM/dd"));
        sbCode.append("\r\n**/\r\n");
    }
}
